package cn.zn.modules.zzsys.cur.service.impl;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.lang.tree.Tree;
import cn.hutool.core.lang.tree.TreeNode;
import cn.hutool.core.lang.tree.TreeNodeConfig;
import cn.hutool.core.lang.tree.TreeUtil;
import cn.hutool.core.util.StrUtil;
import cn.zn.framework.common.vo.CodeNameVO;
import cn.zn.modules.zzsys.cur.mapper.TSysDeptMapper;
import cn.zn.modules.zzsys.cur.service.TSysDeptService;
import cn.zn.modules.zzsys.cur.entity.TSysDept;
import cn.zn.modules.zzsys.his.service.HisBasisDeptService;
import cn.zn.modules.zzsys.inter.DeptInter;
import cn.zn.modules.zzsys.inter.vo.DeptInfoVO;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.common.collect.Maps;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
public class TSysDeptServiceImpl extends ServiceImpl<TSysDeptMapper, TSysDept> implements TSysDeptService, DeptInter {

    @Autowired
    private HisBasisDeptService hisBasisDeptService;

    @Override
    public List<CodeNameVO> deptAll(String deptName) {
        return super.list(new QueryWrapper<TSysDept>().like(StrUtil.isNotEmpty(deptName), "NAME_", deptName))
                .stream().map(o -> CodeNameVO.builder()
                        .code(o.getId())
                        .name(o.getName())
                        .build()).collect(Collectors.toList());
    }

    @Override
    public List<DeptInfoVO> queryForLeaf() {
        return super.list(new QueryWrapper<TSysDept>()
                .eq("IS_LEAF_", true)
                .orderByAsc("SORT_NUM_")).stream().map(o -> {
            DeptInfoVO vo = new DeptInfoVO();
            BeanUtils.copyProperties(o, vo);
            vo.setDeptCode(o.getCode());
            vo.setDeptName(o.getName());
            return vo;
        }).collect(Collectors.toList());
    }

    @Override
    public List<Tree<String>> deptTree(Integer ap, String userId) {
        if (ap == null) {
            return this.deptTree(userId);
        } else {
            return hisBasisDeptService.deptTree(ap, userId);
        }
    }

    @Override
    public List<DeptInfoVO> queryByLoginUser(String userId) {
        return this.baseMapper.queryByLoginUser(userId);
    }

    private List<Tree<String>> deptTree(String userId) {
        List<String> deptIds = CollUtil.newArrayList();
        if (userId != null) {
            HashSet<String> pids = CollUtil.newHashSet();
            deptIds = this.baseMapper.queryByLoginUser(userId).stream().map(o -> {
                pids.add(o.getPid());
                return o.getId();
            }).collect(Collectors.toList());
            deptIds.addAll(CollUtil.newArrayList(pids));
        }
        List<TreeNode<String>> nodeList = super.list(
                new QueryWrapper<TSysDept>()
                        .isNull(deptIds.size() > 0, "PID_")
                        .or().in(deptIds.size() > 0, "ID_", deptIds)
        ).stream().map(o -> {
            Map<String, Object> extra = Maps.newHashMap();
            extra.put("code", o.getCode());
            TreeNode<String> treeNode = new TreeNode<>(o.getId(), o.getPid() == null ? "0" : o.getPid(), o.getName(), o.getSortNum());
            treeNode.setExtra(extra);
            return treeNode;
        }).collect(Collectors.toList());
        TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
        treeNodeConfig.setNameKey("text");
        return TreeUtil.build(nodeList, "0", treeNodeConfig,
                (treeNode, tree) -> {
                    tree.setId(treeNode.getId());
                    tree.setParentId(treeNode.getParentId());
                    tree.setWeight(treeNode.getWeight());
                    tree.setName(treeNode.getName());
                    tree.putExtra("code", treeNode.getExtra().get("code"));
                });
    }
}
